import { ApiProperty } from '@nestjs/swagger'
import {
  IsArray,
  IsEnum,
  IsIn,
  IsInt,
  IsOptional,
  IsString,
  Matches,
  Min,
  MinLength,
} from 'class-validator'

import { PagerDto } from '~/common/dto/pager.dto'
import { CommonStatus, DataScope, RoleType } from '~/enums'
import { IsUnique } from '~/shared/database/constraints/unique.constraint'

import { RoleEntity } from './role.entity'

export class RoleSaveDto {
  @ApiProperty({ description: '角色ID' })
  @IsInt()
  @Min(0)
  @IsOptional()
  id?: number

  @ApiProperty({ description: '角色名称' })
  @IsString()
  @MinLength(2, { message: '角色名称长度不能小于2' })
  name: string

  @IsUnique({ entity: RoleEntity, field: 'code' })
  @ApiProperty({ description: '角色权限字符串' })
  @IsString()
  @Matches(/^\w+$/, { message: '角色权限字符串只能包含字母、数字和下划线，可以是全英文、全数字或字母数字组合' })
  @MinLength(2, { message: '角色权限字符串长度不能小于2' })
  code: string

  @ApiProperty({ description: '显示顺序' })
  @IsInt()
  @Min(0)
  sort: number

  @ApiProperty({ description: '数据范围', enum: DataScope })
  @IsEnum(DataScope)
  dataScope: DataScope

  @ApiProperty({ description: '数据范围(指定部门数组)' })
  @IsString()
  @IsOptional()
  dataScopeDeptIds?: string

  @ApiProperty({ description: '角色状态', enum: CommonStatus })
  @IsEnum(CommonStatus)
  status: CommonStatus

  @ApiProperty({ description: '角色类型', enum: RoleType })
  @IsEnum(RoleType)
  type: RoleType

  @ApiProperty({ description: '角色备注' })
  @IsString()
  @IsOptional()
  remark?: string

  @ApiProperty({ description: '关联菜单、权限编号' })
  @IsOptional()
  @IsArray()
  menuIds?: number[]
}

export class RoleQueryDto extends PagerDto {
  @ApiProperty({ description: '角色名称', required: false })
  @IsString()
  @IsOptional()
  name?: string

  @ApiProperty({ description: '角色权限字符串', required: false })
  @IsString()
  @IsOptional()
  code?: string

  @ApiProperty({ description: '状态', required: false })
  @IsIn([0, 1])
  @IsOptional()
  status?: number
}
